home *** CD-ROM | disk | FTP | other *** search
- // GETINFO SCRIPTING
- // IMDB (US) import - click "Editor" tab to change options
-
- {
- To change the options, go to the "GetOption"
- and "CanSetField" functions
- }
-
- (***************************************************
- * Movie importation script for: *
- * IMDB (US), http://us.imdb.com *
- * *
- * (c) 2002-2005 Antoine Potten *
- * software@antp.be *
- * *
- * For use with Ant Movie Catalog 3.4.3 *
- * www.antp.be/software/moviecatalog *
- * *
- * Based on the script rewritten for version 3.5 *
- * Which was based on the script made for *
- * version 3.3.x / 3.4.x by *
- * Antoine Potten, Danny Falkov, Kai Blankenhorn, *
- * lboregard, Ork, Trekkie, Youri Heijnen *
- * *
- * This program is free software; you can *
- * redistribute it and/or modify it under the *
- * terms of the GNU General Public License as *
- * published by the Free Software Foundation; *
- * either version 2 of the License, or (at your *
- * option) any later version. *
- ***************************************************)
-
- program IMDB;
-
- // ***** Here you can change the options of the script *****
-
- function GetOption(OptName: string): Integer;
- begin
- case OptName of
- 'ImageKind': Result := 2;
- {
- 0=No image
- 1=IMDB small image, from the main movie page
- 2=IMDB large image if found easily, else small image
- 3=First search for Amazon large image, then IMDB large one, then IMDB small image if other failed
- 4=First search for Amazon large image, then directly take IMDB small image if the first one failed
- 5=IMDB large image if found easily, else search for Amazon large image, then take IMDB small image if others failed
- }
- 'BatchMode': Result := 0;
- {
- 0=Normal working mode, prompts user when needed
- 1=Does not display any window, takes the first movie found
- }
- 'PopularSearches': Result := 1;
- {
- 0=Do not use the popular searches page, directly show full search results
- 1=Show popular searches first, I'll click on "Find more" if needed
- }
- 'ActorsLayout': Result := 0;
- {
- 0=Only actor names, separated by commas
- 1=Only actor names, separated by linebreaks
- 2=Actors names with character names between parenthesis separated by commas
- 3=Actors names with character names between parenthesis separated by linebreaks
- 4=Actor names like on IMDB page, with "...." and separated by linebreaks
- }
- 'MultipleValuesCountry': Result := 0;
- {
- 0=Only take first value for Country
- 1=Take full list, separated by commas
- 2=Take full list, separated by slashes
- }
- 'MultipleValuesCategory': Result := 0;
- {
- 0=Only take first value for Category
- 1=Take full list, separated by commas
- 2=Take full list, separated by slashes
- }
- 'MultipleValuesLanguages': Result := 0;
- {
- 0=Only take first value for Languages
- 1=Take full list, separated by commas
- 2=Take full list, separated by slashes
- }
- 'DescriptionSelection': Result := 2;
- {
- 0=Take the short summary, from main page (faster)
- 1=Show a list of available summaries
- 2=Take the longest summary
- }
- 'GetTagline': Result := 0;
- {
- 0=Do not get tagline
- 1=Put it in Description field, before the summary
- 2=Put it in the Comment field, before the comments
- }
- end;
- end;
-
- // Here you can specify which fields can be modified.
- // Simply remove a field from the list if it cannot be modified
-
- function CanSetField(fieldID: Integer): Boolean;
- begin
- case fieldID of
- fieldNumber,
- fieldMedia,
- fieldMediaType,
- fieldSource,
- fieldDate,
- fieldBorrower,
- fieldRating,
- fieldOriginalTitle,
- fieldTranslatedTitle,
- fieldDirector,
- fieldProducer,
- fieldCountry,
- fieldCategory,
- fieldYear,
- fieldLength,
- fieldActors,
- fieldURL,
- fieldDescription,
- fieldComments,
- fieldVideoFormat,
- fieldVideoBitrate,
- fieldAudioFormat,
- fieldAudioBitrate,
- fieldResolution,
- fieldFrameRate,
- fieldLanguages,
- fieldSubtitles,
- fieldSize,
- fieldDisks: Result := True;
- else
- Result := False;
- end;
- end;
-
- var
- MovieName: string;
- MovieURL: string;
- MovieNumber: string;
-
- var
- RemainingText: string;
- {
- when calling... this variable contains...
- TextBefore the text after SearchText
- TextBetween the text after AfterText
- }
-
- // ***** Like the Pos function, but returns the last occurence instead of the first one *****
-
- function LastPos(ASearch: string; AText: string): Integer;
- var
- CurPos, PrevPos: Integer;
- begin
- PrevPos := 0;
- CurPos := Pos(ASearch, AText);
- while CurPos > 0 do
- begin
- if PrevPos = 0 then
- PrevPos := CurPos
- else
- PrevPos := PrevPos + CurPos + Length(ASearch) - 1;
- Delete(AText, 1, CurPos + Length(ASearch) - 1);
- CurPos := Pos(ASearch, AText);
- end;
- Result := PrevPos;
- end;
-
- // *****
- { Returns the text before SearchText, but not before BeginLimit (if it is not empty),
- It takes the last occurence of BeginLimit found before the position of SearchText }
-
- function TextBefore(WholeText: string; SearchText: string; BeginLimit: string): string;
- var
- FoundPos, PrevPos: Integer;
- WorkText: string;
- begin
- Result := '';
- FoundPos := Pos(SearchText, WholeText);
- if FoundPos = 0 then
- Exit;
- WorkText := Copy(WholeText, 1, FoundPos - 1);
- RemainingText := Copy(WholeText, FoundPos + Length(SearchText), Length(WholeText));
- if BeginLimit <> '' then
- begin
- FoundPos := LastPos(BeginLimit, WorkText);
- if FoundPos = 0 then
- Exit
- else
- FoundPos := FoundPos + Length(BeginLimit);
- end
- else
- FoundPos := 1;
- Result := Copy(WorkText, FoundPos, Length(WorkText));
- end;
-
- // ***** Returns the text after SearchText *****
-
- function TextAfter(WholeText: string; SearchText: string): string;
- var
- FoundPos: Integer;
- begin
- Result := '';
- FoundPos := Pos(SearchText, WholeText);
- if FoundPos = 0 then
- Exit;
- Result := Copy(WholeText, FoundPos + Length(SearchText), Length(WholeText));
- end;
-
- // *****
- { Returns the text between BeforeText and AfterText (without these two strings),
- It takes the first AfterText occurence found after the position of BeforeText }
-
- function TextBetween(WholeText: string; BeforeText: string; AfterText: string): string;
- var
- FoundPos: Integer;
- WorkText: string;
- begin
- Result := '';
- FoundPos := Pos(BeforeText, WholeText);
- if FoundPos = 0 then
- Exit;
- WorkText := Copy(WholeText, FoundPos + Length(BeforeText), Length(WholeText));
- FoundPos := Pos(AfterText, WorkText);
- if FoundPos = 0 then
- Exit;
- Result := Copy(WorkText, 1, FoundPos - 1);
- RemainingText := Copy(WorkText, FoundPos + Length(AfterText), Length(WorkText));
- end;
-
- // ***** analyzes the results page that asks to select a movie from a list *****
-
- procedure AnalyzeResultsPage(Address: string);
- var
- PageText: string;
- Value: string;
- begin
- PageText := GetPage(Address);
- if pos('<title>IMDb', PageText) = 0 then
- begin
- AnalyzeMoviePage(PageText)
- end else
- begin
- if Pos('<b>No Matches.</b>', PageText) > 0 then
- begin
- if GetOption('BatchMode') = 0 then
- ShowMessage('No movie found for this search');
- Exit;
- end;
- PickTreeClear;
- repeat
- Value := TextBefore(PageText, '<ol>', '<b>');
- if Value <> '' then
- begin
- HTMLRemoveTags(Value);
- HTMLDecode(Value);
- PickTreeAdd(Value, '');
- end;
- Value := TextBetween(PageText, '<ol>', '</ol>');
- PageText := RemainingText;
- until not AddMovieTitles(Value);
- Value := TextBefore(PageText, '"><b>more titles</b></a>', '<a href="');
- if Value <> '' then
- PickTreeMoreLink('http://us.imdb.com' + Value);
- if PickTreeExec(Address) then
- AnalyzeResultsPage(Address);
- end;
- end;
-
- // ***** adds the titles contained in <ol>'s items *****
-
- function AddMovieTitles(List: string): Boolean;
- var
- Value: string;
- Address: string;
- begin
- Result := False;
- Value := TextBetween(List, '<li>', '</li>');
- List := RemainingText;
- while Value <> '' do
- begin
- Address := TextBetween(Value, '<a href="', '">');
- HTMLRemoveTags(Value);
- HTMLDecode(Value);
- PickTreeAdd(Value, 'http://us.imdb.com' + Address);
- Result := True;
- Value := TextBetween(List, '<li>', '</li>');
- List := RemainingText;
- end;
- end;
-
- // ***** analyzes the page containing movie information *****
-
- procedure AnalyzeMoviePage(PageText: string);
- var
- Value, Value2, Value3, FullValue: string;
- begin
- MovieNumber := TextBetween(PageText, '<input type="hidden" name="arg" value="', '"><input');
- MovieURL := 'http://us.imdb.com/title/tt' + MovieNumber;
- // URL
- if CanSetField(fieldURL) then
- SetField(fieldURL, MovieURL);
- // Original Title & Year
- if CanSetField(fieldOriginalTitle) or CanSetField(fieldYear) then
- begin
- Value := TextBetween(PageText, '<title>', '</title>');
- Value2 := TextBefore(Value, ' (', '');
- Value := RemainingText;
- HTMLDecode(Value2);
- if CanSetField(fieldOriginalTitle) then
- SetField(fieldOriginalTitle, Value2);
- if Pos('/', Value) > 0 then
- Value2 := TextBefore(Value, '/', '')
- else
- Value2 := TextBefore(Value, ')', '');
- if CanSetField(fieldYear) then
- SetField(fieldYear, Value2);
- end;
- // Rating
- if CanSetField(fieldRating) then
- begin
- Value := TextBetween(PageText, '/rating-stars/', '/rating-vote/');
- Value2 := TextBetween(Value, '<b>', '.');
- if StrToInt(Copy(RemainingText, 1, 1), 0) >= 5 then
- Value2 := IntToStr(StrToInt(Value2, 0) + 1);
- SetField(fieldRating, Value2);
- end;
- // Picture
- case GetOption('ImageKind') of
- 1: ImportSmallPicture(PageText);
- 2: if not ImportLargePicture('http://us.imdb.com/gallery/ss/' + MovieNumber) then
- ImportSmallPicture(PageText);
- 3: if not ImportAmazonPicture(PageText) then
- if not ImportLargePicture('http://us.imdb.com/gallery/ss/' + MovieNumber) then
- ImportSmallPicture(PageText);
- 4: if not ImportAmazonPicture(PageText) then
- ImportSmallPicture(PageText);
- 5: if not ImportLargePicture('http://us.imdb.com/gallery/ss/' + MovieNumber) then
- if not ImportAmazonPicture(PageText) then
- ImportSmallPicture(PageText);
- end;
- // Director
- if CanSetField(fieldDirector) then
- begin
- Value := TextBetween(PageText, '<b class="blackcatheader">Directed by</b>', '</a>');
- Value := StringReplace(TextAfter(Value, '">'), '<br>', ', ');
- HTMLRemoveTags(Value);
- HTMLDecode(Value);
- SetField(fieldDirector, Value);
- end;
- // Actors
- if CanSetField(fieldActors) then
- begin
- Value := TextBetween(PageText, 'ast overview', '</div>');
- if Value = '' then
- Value := TextBetween(PageText, 'redited cast', '</div>');
- if Value <> '' then
- begin
- Value := TextAfter(Value, '</tr> ');
- FullValue := '';
- case GetOption('ActorsLayout') of
- 0, 1:
- while Pos('<tr>', Value) > 0 do
- begin
- Value2 := TextBetween(Value, '<tr>', '</tr>');
- Value := RemainingText;
- if Pos('<a href="fullcredits">(more)</a>', Value2) > 0 then
- Break;
- if FullValue <> '' then
- FullValue := FullValue + #13#10;
- FullValue := FullValue + TextBefore(Value2, '</td>', '');
- end;
- 2, 3:
- while Pos('<tr>', Value) > 0 do
- begin
- Value2 := TextBetween(Value, '<tr>', '</tr>');
- Value := RemainingText;
- if Pos('<a href="fullcredits">(more)</a>', Value2) > 0 then
- Break;
- if FullValue <> '' then
- FullValue := FullValue + #13#10;
- FullValue := FullValue + TextBefore(Value2, '</td>', '');
- Value2 := TextBetween(RemainingText, '<td valign="top">', '</td>');
- if Value2 <> '' then
- FullValue := FullValue + ' (as ' + Value2 + ')';
- end;
- 4:
- begin
- FullValue := TextBefore(Value, '</tr><tr><td colspan="2">', '');
- if FullValue = '' then
- FullValue := Value;
- FullValue := StringReplace(FullValue, '</tr>', #13#10);
- end;
- end;
- HTMLRemoveTags(FullValue);
- HTMLDecode(FullValue);
- case GetOption('ActorsLayout') of
- 0, 2:
- FullValue := StringReplace(FullValue, #13#10, ', ');
- end;
- SetField(fieldActors, FullValue);
- end;
- end;
- //Country
- if CanSetField(fieldCountry) then
- begin
- SetField(fieldCountry, ImportList(PageText, GetOption('MultipleValuesCountry'), '/Countries/'));
- end;
- //Category
- if CanSetField(fieldCategory) then
- begin
- SetField(fieldCategory, ImportList(PageText, GetOption('MultipleValuesCategory'), '/Genres/'));
- end;
- // Language
- if CanSetField(fieldLanguages) then
- begin
- SetField(fieldLanguages, ImportList(PageText, GetOption('MultipleValuesLanguages'), '/Languages/'));
- end;
- //Description
- if CanSetField(fieldDescription) then
- begin
- Value := TextBetween(PageText, '<b class="ch">Plot Outline:</b>', '<br><br>');
- if Value = '' then
- Value := TextBetween(PageText, '<b class="ch">Plot Summary:</b>', '<br><br>');
- if Value <> '' then
- SetField(fieldDescription, ImportSummary(Value));
- end;
- // Comments
- if CanSetField(fieldComments) then
- begin
- Value := TextAfter(PageText, '/comments">');
- if Value <> '' then
- begin
- Value := TextBetween(Value, '<p>', '</p>');
- Value := StringReplace(Value, #13#10, ' ');
- Value := StringReplace(Value, '<br>', #13#10);
- HTMLRemoveTags(Value);
- HTMLDecode(Value);
- Value := Trim(Value);
- while Pos(' ', Value) > 0 do
- Value := StringReplace(Value, ' ', ' ');
- while Pos(#13#10, Value) = 1 do
- Delete(Value, 1, 2);
- SetField(fieldComments, Value);
- end;
- end;
- // Length
- if CanSetField(fieldLength) then
- begin
- Value := TextBetween(PageText, '<b class="ch">Runtime:</b>' + #13#10, ' ');
- if Value <> '' then
- begin
- if Pos(':', Value) > 0 then
- SetField(fieldLength, TextAfter(Value, ':'))
- else
- SetField(fieldLength, Value);
- end;
- end;
- // TagLine
- if GetOption('GetTagline') > 0 then
- begin
- Value := TextBetween(PageText, 'Tagline:</b>', #13);
- if Pos('<a', Value) > 0 then
- Value := TextBefore(Value, '<a', '');
- HTMLRemoveTags(Value);
- HTMLDecode(Value);
- Value := Trim(Value);
- if Value <> '' then
- begin
- Value := '"' + Value + '"';
- case GetOption('GetTagline') of
- 1:
- if CanSetField(fieldDescription) then
- SetField(fieldDescription, Value + #13#10 + GetField(fieldDescription));
- 2:
- if CanSetField(fieldComments) then
- SetField(fieldComments, Value + #13#10 + GetField(fieldComments));
- end;
- end;
- end;
- end;
-
- // ***** Imports lists like Genre, Country, etc. depending of the selected option *****
-
- function ImportList(PageText: string; MultipleValues: Integer; StartTag: string): string;
- var
- Value, Value2: string;
- begin
- if MultipleValues = 0 then
- begin
- Value := TextBetween(PageText, StartTag, '</a>');
- Value2 := TextAfter(Value, '">');
- end
- else
- begin
- Value := TextBetween(PageText, StartTag, #13#10);
- Value2 := TextBefore(Value, ' <a href="/rg', '');
- if Value2 <> '' then
- Value := Value2;
- Value2 := TextAfter(Value, '">');
- HTMLRemoveTags(Value2);
- if MultipleValues = 1 then
- Value2 := StringReplace(Value2, ' / ', ', ');
- end;
- HTMLDecode(Value2);
- Result := Value2;
- end;
-
- // ***** functions to import the different pictures kinds, depending of the option selected by user *****
-
- function ImportSmallPicture(PageText: string): Boolean;
- var
- Value: string;
- begin
- Result := False;
- Value := TextBetween(PageText, '<img border="0" alt="cover" src="', '"');
- if Value <> '' then
- begin
- GetPicture(Value, False);
- Result := True;
- end;
- end;
-
- function ImportLargePicture(Address: string): Boolean;
- var
- Value, Value2: string;
- begin
- Result := True;
- Value := GetPage(Address);
- if SearchForLargePicture(Value, 'Onesheet_text', False) then
- Exit;
- if SearchForLargePicture(Value, 'Onesheet', False) then
- Exit;
- if SearchForLargePicture(Value, 'poster', False) then
- Exit;
- if SearchForLargePicture(Value, 'keyart01', False) then
- Exit;
- if SearchForLargePicture(Value, 'usposter', False) then
- Exit;
- if SearchForLargePicture(Value, 'text', True) then
- Exit;
- if SearchForLargePicture(Value, 'pos01', True) then
- Exit;
- if SearchForLargePicture(Value, 'KeyArt', True) then
- Exit;
- if SearchForLargePicture(Value, 'heet', True) then // Sheet & Onesheet
- Exit;
- if SearchForLargePicture(Value, 'OneSheetv2', True) then
- Exit;
- if SearchForLargePicture(Value, 'artwork', True) then
- Exit;
- Address := TextBetween(Value, 'There are ' + #13#10 + '<a href="', '">');
- if Address <> '' then
- Result := ImportLargePicture('http://us.imdb.com' + Address)
- else
- Result := False;
- end;
-
- function SearchForLargePicture(PageText: string; Name: string; PartialName: Boolean): Boolean;
- var
- Value: string;
- begin
- Result := False;
- if PartialName then
- begin
- Value := TextBefore(PageText, Name + '.jpg', '/');
- if Value = '' then
- Exit
- else
- Name := Value + Name;
- end;
- Value := TextBefore(PageText, 'th-' + Name + '.jpg', 'src="');
- if Value <> '' then
- begin
- GetPicture(Value + Name + '.jpg', False);
- Result := True;
- end;
- end;
-
- function ImportAmazonPicture(PageText: string): Boolean;
- var
- Value, Value2: string;
- begin
- Result := False;
- Value := TextBefore(PageText, '" title="DVD available', '<a href="');
- if Value = '' then
- Exit;
- PageText := GetPage('http://us.imdb.com' + Value);
- if Pos('unable to find exact matches', PageText) > 0 then
- Exit;
- if Pos('You may also be interested in these items...', PageText) > 0 then
- PageText := TextBefore(PageText, 'You may also be interested in these items...', '');
- Value := TextBefore(PageText, 'TZZZZZZZ.jpg', '<img src="');
- if Value = '' then
- Value := TextBefore(PageText, 'THUMBZZZ.jpg', '<img src="');
- if Value <> '' then
- begin
- GetPicture(Value + 'LZZZZZZZ.jpg', False);
- Result := True;
- end;
- end;
-
- // ***** Gets summaries for the movie, based on the plot outline given in parameter (that contains the URL to more summaries) *****
-
- function ImportSummary(PlotText: string): string;
- var
- Address, Value, Value2, PageText, Longest: string;
- begin
- Address := TextBetween(PlotText, '<a href="/rg/title-tease/plotsummary', '">(more)</a>');
- if (Address = '') or (GetOption('DescriptionSelection') = 0) then
- begin
- Result := Trim(TextBefore(PlotText, '<a href="/rg', ''));
- if Result = '' then
- Result := Trim(PlotText);
- HTMLRemoveTags(Result);
- HTMLDecode(Result);
- end
- else
- begin
- PageText := GetPage('http://us.imdb.com/rg/title-tease/plotsummary' + Address);
- PickListClear;
- Longest := '';
- Value := TextBetween(PageText, '<p class="plotpar">', '</p>');
- PageText := RemainingText;
- while Value <> '' do
- begin
- Value := StringReplace(Value, #13#10, ' ');
- Value := StringReplace(Value, '<br>', #13#10);
- HTMLRemoveTags(Value);
- HTMLDecode(Value);
- while Pos(' ', Value) > 0 do
- Value := StringReplace(Value, ' ', ' ');
- if Length(Value) > Length(Longest) then
- Longest := Value;
- PickListAdd(Trim(Value));
- Value := TextBetween(PageText, '<p class="plotpar">', '</p>');
- PageText := RemainingText;
- end;
- if (GetOption('BatchMode') = 1) or (GetOption('DescriptionSelection') = 2) then
- Result := Longest
- else
- begin
- if not PickListExec('Select a description for "' + GetField(fieldOriginalTitle) + '"', Result) then
- Result := '';
- end;
- end;
- end;
-
- // ***** beginning of the program *****
-
- begin
- if CheckVersion(3,4,3) then
- begin
- MovieName := GetField(fieldOriginalTitle);
- if MovieName = '' then
- MovieName := GetField(fieldTranslatedTitle);
- if GetOption('BatchMode') = 0 then
- begin
- if not Input('IMDB Import', 'Enter the title or the IMDB URL of the movie:', MovieName) then
- Exit;
- end;
- if MovieName <> '' then
- begin
- if Pos('imdb.com', MovieName) > 0 then
- AnalyzeResultsPage(MovieName)
- else
- begin
- MovieName := StringReplace(MovieName, '&', 'and');
- if (GetOption('BatchMode') = 1) or (GetOption('PopularSearches') = 1) then
- AnalyzeResultsPage('http://us.imdb.com/find?tt=1;q=' + UrlEncode(MovieName))
- else
- AnalyzeResultsPage('http://us.imdb.com/find?more=tt;q=' + UrlEncode(MovieName));
- end;
- DisplayResults;
- end;
- end
- else
- ShowMessage('This script requires a newer version of Ant Movie Catalog (at least the version 3.4.3)');
- end.
-